#include <bits/stdc++.h>
using namespace std;
#define int long long
#define ls(p) (p << 1)
#define rs(p) (p << 1 | 1)
int n, k, d, a[500005], b[500005];

namespace CR200J {
	int dp[10001];
	int dfs(int i) {
		if (i == n) return a[i];
		if (dp[i] != -1) return dp[i];
		int ans = -1ll << 60;
		for (int j = i + 1; j <= i + b[i]; ++j)
			ans = max(ans, dfs(j) - (j - i) / k * d);
		return dp[i] = ans + a[i];
	}
	void main() {
		memset(dp, 255, sizeof(dp));
		cout << dfs(1) << "\n";
	}
}

namespace CR400AF {
	struct Info {
		int res[5];
		Info operator + (const Info &a) const {
			Info s = a;
			for (int i = 0; i < 5; ++i) s.res[i] = max(s.res[i], res[i]);
			return s;
		}
		void clt(int tot) {
			Info ns = {};
			for (int i = 0; i < k; ++i) {
				ns.res[(i + tot) % k] = max(-1ll << 60, res[i] - d * ((i + tot) / k));
			}
			for (int i = 0; i < k; ++i) {
				res[i] = ns.res[i];
			}
		}
	} t[500005*4];
	int tag[500005*4];
	struct SGT {
		void settag(int i, int k) {
			t[i].clt(k);
			tag[i] += k;
		}
		void push_down(int i) {
			if (tag[i]) {
				settag(ls(i), tag[i]);
				settag(rs(i), tag[i]);
				tag[i] = 0;
			}
		}
		void push_up(int i) {
			t[i] = t[ls(i)] + t[rs(i)];
		}
		void update(int i, int l, int r, int ql, int qr) {
			if (l > qr || r < ql) return;
			if (l >= ql && r <= qr) return settag(i, 1);
			int mid = (l + r) / 2; push_down(i);
			update(ls(i), l, mid, ql, qr);
			update(rs(i), mid + 1, r, ql, qr);
			push_up(i);
		}
		void update_pos(int i, int l, int r, int qpos, int v) {
			if (l > qpos || r < qpos) return;
			if (l == r) {
				t[i].res[0] = max(t[i].res[0], v);
				return;
			}
			int mid = (l + r) / 2; push_down(i);
			update_pos(ls(i), l, mid, qpos, v);
			update_pos(rs(i), mid + 1, r, qpos, v);
			push_up(i);
		}
		Info query(int i, int l, int r, int ql, int qr) {
			if (l > qr || r < ql) return {{-1ll << 60, -1ll << 60, -1ll << 60, -1ll << 60, -1ll << 60}};
			if (l >= ql && r <= qr) return t[i];
			int mid = (l + r) / 2; push_down(i);
			return query(ls(i), l, mid, ql, qr) + query(rs(i), mid + 1, r, ql, qr);
		}
	} trs;
	void main() {
		for (int i = 0; i < 500005*4; ++i) {
			t[i] =  {{-1ll << 60, -1ll << 60, -1ll << 60, -1ll << 60, -1ll << 60}};
		}
		trs.update_pos(1, 1, n, n, a[n]);
		trs.update(1, 1, n, n, n);
		for (int i = n - 1; i >= 1; --i) {
			Info res = trs.query(1, 1, n, i + 1, i + b[i]);
			int mx = -1ll << 60;
			for (int i = 0; i < k; ++i) {
				mx = max(mx, res.res[i]);
			}
			mx += a[i];
			if (i == 1) cout << mx << "\n";
			trs.update_pos(1, 1, n, i, mx);
			trs.update(1, 1, n, i, n);
		}
	}
}
namespace CR400BF {
	int res[500005*4];
	struct SGT {
		void push_up(int i) {
			res[i] = max(res[ls(i)], res[rs(i)]);
		}
		void update_pos(int i, int l, int r, int qpos, int v) {
			if (l > qpos || r < qpos) return;
			if (l == r) {
				res[i] = max(res[i], v);
				return;
			}
			int mid = (l + r) / 2;
			update_pos(ls(i), l, mid, qpos, v);
			update_pos(rs(i), mid + 1, r, qpos, v);
			push_up(i);
		}
		int query(int i, int l, int r, int ql, int qr) {
			if (l > qr || r < ql) return -1ll << 60;
			if (l >= ql && r <= qr) return res[i];
			int mid = (l + r) / 2;
			return max(query(ls(i), l, mid, ql, qr), query(rs(i), mid + 1, r, ql, qr));
		}
	} trs;
	void main() {
		for (int i = 0; i < 500005*4; ++i) {
			res[i] = -1ll << 60 ;
		}
		trs.update_pos(1, 1, n, n, a[n]);
		for (int i = n - 1; i >= 1; --i) {
			int mx = -1ll << 60;
			for (int j = i + 1; j <= i + b[i]; ++j) {
				int r = min(i + b[i], (j - i) + (k - (j - i) % k) - 1 + i);
				/*
				   1 2 3 4 5 6
				   2 2 5 5 5
				*/
				assert((r - i) / k == (j - i) / k);
				mx = max(mx, trs.query(1, 1, n, j, min(i + b[i], r)) - (r - i) / k * d);
				j = r;
			}
			mx += a[i];
			if (i == 1) cout << mx << "\n";
			trs.update_pos(1, 1, n, i, mx);
		}
	}
}
namespace BF5033 {
	int res[500005*4];
	struct SGT {
		void push_up(int i) {
			res[i] = max(res[ls(i)], res[rs(i)]);
		}
		void update_pos(int i, int l, int r, int qpos, int v) {
			if (l > qpos || r < qpos) return;
			if (l == r) {
				res[i] = max(res[i], v);
				return;
			}
			int mid = (l + r) / 2;
			update_pos(ls(i), l, mid, qpos, v);
			update_pos(rs(i), mid + 1, r, qpos, v);
			push_up(i);
		}
		int query(int i, int l, int r, int ql, int qr) {
			if (l > qr || r < ql) return -1ll << 60;
			if (l >= ql && r <= qr) return res[i];
			int mid = (l + r) / 2;
			return max(query(ls(i), l, mid, ql, qr), query(rs(i), mid + 1, r, ql, qr));
		}
	} trs;
	void main() {
		for (int i = 0; i < 500005*4; ++i) {
			res[i] = -1ll << 60 ;
		}
		trs.update_pos(1, 1, n, n, a[n]);
		for (int i = n - 1; i >= 1; --i) {
			int mx = -1ll << 60;
			for (int j = i + 1; j <= min(i + 1 + k * 3, i + b[i]); ++j) {
				int r = min(i + b[i], (j - i) + (k - (j - i) % k) - 1 + i);
				/*
				   1 2 3 4 5 6
				   2 2 5 5 5
				*/
				mx = max(mx, trs.query(1, 1, n, j, min(i + b[i], r)) - (r - i) / k * d);
				j = r;
			}
			for (int j = max(i + 1, i + b[i] - k * 1); j <= i + b[i]; ++j) {
				int r = min(i + b[i], (j - i) + (k - (j - i) % k) - 1 + i);
				/*
				   1 2 3 4 5 6
				   2 2 5 5 5
				*/
				mx = max(mx, trs.query(1, 1, n, j, min(i + b[i], r)) - (r - i) / k * d);
				j = r;
			}
			mx += a[i];
			if (i == 1) cout << mx << "\n";
			trs.update_pos(1, 1, n, i, mx);
		}
	}
}

signed main() {
	freopen("holiday.in", "r", stdin); freopen("holiday.out", "w", stdout);
	ios::sync_with_stdio(0); cin.tie(0); cout.tie(0);
	cin >> n >> k >> d;
	for (int i = 1; i <= n; ++i) {
		cin >> a[i];
	}
	for (int i = 1; i <= n - 1; ++i) {
		cin >> b[i];
	}
	if (n <= 5000) {
		CR200J::main();
	} else if (n <= 50000) {
		CR400BF::main();
	} else if (k <= 5) {
		CR400AF::main();
	} else {
		BF5033::main();
	}
	return 0;
}
